//
//  GJLocationUtil.m
//  xmgjAppFront
//
//  Created by Zeki on 2020/7/9.
//  Copyright © 2020 guojutech. All rights reserved.
//

#import "GJLocationUtil.h"
#import <YYModel/YYModel.h>
//高德地图
#import <AMapFoundationKit/AMapFoundationKit.h>
#import <AMapLocationKit/AMapLocationKit.h>
#import <AMapFoundationKit/AMapFoundationKit.h>
#import <AMapSearchKit/AMapSearchKit.h>

@interface GJLocationUtil ()<AMapLocationManagerDelegate,AMapSearchDelegate>
@property (nonatomic, strong)AMapLocationManager *locationManager;
@property (nonatomic, strong)AMapSearchAPI *search;

/// 定位
@property (nonatomic, copy)void (^updateLocationBlock)(CLLocationCoordinate2D coordinate,NSDictionary *addressDic,NSError *error);

/// 地址编码
@property (nonatomic, copy)void (^getGeoCodeBlcok)(NSArray *resultArray);

///逆地理编码
//@property (nonatomic, copy)void (^reGeoCompleteBlock)(BMKReverseGeoCodeSearchResult * result, NSInteger errorCode);
///关键字poi
@property (nonatomic, copy)void (^keyWordsPoiSearchBlock)(NSArray *resultArray);
@end

@implementation GJLocationUtil


+ (instancetype)shareInstance{
  static GJLocationUtil *util = nil;
  static dispatch_once_t oncetoken;
  dispatch_once(&oncetoken, ^{
    util = [GJLocationUtil new];
  });
  return util;
}
- (void)getLocationWithCommplete:(void (^)(CLLocationCoordinate2D, NSDictionary * _Nonnull, NSError * _Nonnull))locationCompleteBlock{
  [self startSerialLocation];
  self.updateLocationBlock = locationCompleteBlock;
}

- (void)geocodeSearch:(NSDictionary *)addressDic commplete:(void (^)(NSArray * _Nonnull))commpleteBlock{
  
  AMapGeocodeSearchRequest *geo = [[AMapGeocodeSearchRequest alloc] init];
  
  NSString *city = addressDic[@"city"];
  NSString *country = addressDic[@"country"];
  geo.city = city;
  geo.country = country;
  [self.search AMapGeocodeSearch:geo];
  self.getGeoCodeBlcok = commpleteBlock;
}

- (void)searchPOIWithKeyWords:(NSString *)keywords city:(NSString *)city complete:(void (^)(NSArray * _Nonnull))completeBlock{
  AMapPOIKeywordsSearchRequest *request = [[AMapPOIKeywordsSearchRequest alloc] init];
  request.keywords            = keywords;
  request.city                = city;
  request.requireExtension    = YES;
  /*  搜索SDK 3.2.0 中新增加的功能，只搜索本城市的POI。*/
//  request.cityLimit           = YES;
//  request.requireSubPOIs      = YES;
  [self.search AMapPOIKeywordsSearch:request];
  self.keyWordsPoiSearchBlock = completeBlock;
}
- (void)searchPOIWithCoordinate:(CLLocationCoordinate2D)coordinate  city:(NSString *)city complete:(void (^)(NSArray * _Nonnull))completeBlock{
  AMapPOIAroundSearchRequest *request = [[AMapPOIAroundSearchRequest alloc] init];
  request.location = [AMapGeoPoint locationWithLatitude:coordinate.latitude longitude:coordinate.longitude];
  request.requireExtension    = YES;
//  request.radius = 1000;
  /*  搜索SDK 3.2.0 中新增加的功能，只搜索本城市的POI。*/
//  request.cityLimit           = YES;
//  request.requireSubPOIs      = YES;
  [self.search AMapPOIAroundSearch:request];
  self.keyWordsPoiSearchBlock = completeBlock;
}

#pragma mark -- amapActions&&delegate
- (void)startSerialLocation {
  [self.locationManager startUpdatingLocation];
}

- (void)stopSerialLocation{
  [self.locationManager stopUpdatingLocation];
}

- (void)amapLocationManager:(AMapLocationManager *)manager didFailWithError:(NSError *)error {
  self.updateLocationBlock(CLLocationCoordinate2DMake(0, 0), @{}, error);
}


- (void)amapLocationManager:(AMapLocationManager *)manager didUpdateLocation:(CLLocation *)location reGeocode:(AMapLocationReGeocode *)reGeocode
{
  AMapReGeocodeSearchRequest *request = [[AMapReGeocodeSearchRequest alloc]init];
  request.location = [AMapGeoPoint locationWithLatitude:location.coordinate.latitude longitude:location.coordinate.longitude];
  request.requireExtension    = YES;
  request.radius = 1000;
  [self.search AMapReGoecodeSearch:request];
}
#pragma mark -- AMapSearchDelegate
- (void)onGeocodeSearchDone:(AMapGeocodeSearchRequest *)request response:(AMapGeocodeSearchResponse *)response{
  if (response.geocodes.count > 0) {
    self.getGeoCodeBlcok(@[]);
  }else{
    NSMutableArray *tempArray = [NSMutableArray array];
    [response.geocodes each:^(AMapGeocode* object) {
      NSDictionary *tempDic = [object yy_modelToJSONObject];
      [tempArray addObject:tempDic];
    }];
    self.getGeoCodeBlcok([tempArray mutableCopy]);
  }
  
}

- (void)onPOISearchDone:(AMapPOISearchBaseRequest *)request response:(AMapPOISearchResponse *)response{
  if (response.pois.count == 0)
  {
    self.keyWordsPoiSearchBlock(@[]);
  }else{
    NSMutableArray *tempArray = [NSMutableArray array];
       [response.pois each:^(AMapPOI* object) {
         NSMutableDictionary *blockDic = [NSMutableDictionary new];
         [blockDic setObject:@(object.location.latitude) forKey:@"latitude"];
         [blockDic setObject:@(object.location.longitude) forKey:@"longitude"];
         [blockDic setObject:object.province forKey:@"province"];
         [blockDic setObject:object.city forKey:@"city"];
         [blockDic setObject:object.district forKey:@"area"];
         [blockDic setObject:object.district forKey:@"district"];
         [blockDic setObject:object.address forKey:@"street"];
         [blockDic setObject:object.name forKey:@"name"];
         [blockDic setObject:object.adcode forKey:@"adCode"];
         [blockDic setObject:[NSString stringWithFormat:@"%@%@%@%@",object.province,object.city,object.district,object.address] forKey:@"address"];
         [tempArray addObject:blockDic];
       }];
    if (self.keyWordsPoiSearchBlock) {
       self.keyWordsPoiSearchBlock([tempArray mutableCopy]);
    }
  }
}
- (void)onReGeocodeSearchDone:(AMapReGeocodeSearchRequest *)request response:(AMapReGeocodeSearchResponse *)response{
  if (self.updateLocationBlock) {
    AMapReGeocode *reGeoCode = response.regeocode;
    NSString *formattedAddress = reGeoCode.formattedAddress;
    AMapPOI *poi = reGeoCode.pois.firstObject;
    NSString *poiStr = poi.name;
    NSDictionary *addressDic = [reGeoCode.addressComponent mj_JSONObject];
    
    
    NSMutableDictionary *blockDic = [NSMutableDictionary new];
    [blockDic setObject:@(request.location.latitude) forKey:@"latitude"];
    [blockDic setObject:@(request.location.longitude) forKey:@"longitude"];
    [blockDic setObject:addressDic[@"province"] forKey:@"province"];
    [blockDic setObject:addressDic[@"city"] forKey:@"city"];
    [blockDic setObject:addressDic[@"district"] forKey:@"district"];
    [blockDic setObject:addressDic[@"township"] forKey:@"street"];
    [blockDic setObject:[addressDic[@"streetNumber"] objectForKey:@"direction"] forKey:@"direction"];
    [blockDic setObject:formattedAddress forKey:@"addressDetail"];
    [blockDic setObject:poiStr forKey:@"poiStr"];
    self.updateLocationBlock(CLLocationCoordinate2DMake(request.location.latitude, request.location.longitude), blockDic, nil);
    self.updateLocationBlock = nil;
  }
}

#pragma mark -- getter
- (AMapLocationManager *)locationManager{
  if (!_locationManager) {
    _locationManager = [[AMapLocationManager alloc] init];
    [_locationManager setDelegate:self];
    [_locationManager setPausesLocationUpdatesAutomatically:NO];
    _locationManager.locatingWithReGeocode = YES;
    _locationManager.distanceFilter = 200;
  }
  return _locationManager;
}
-(AMapSearchAPI *)search{
  if (!_search) {
    _search = [[AMapSearchAPI alloc] init];
    _search.delegate = self;
  }
  return _search;
}



#pragma mark - 根据所有的大头针坐标,计算显示范围,屏幕能够刚好显示大头针
#define CW_MINIMUM_ZOOM_ARC 0.014
#define CW_ANNOTATION_REGION_PAD_FACTOR 1.15
#define CW_MAX_DEGREES_ARC 360
- (void)zoomMapViewToFitAnnotations:(MAMapView *)mapView animated:(BOOL)animated
{
    NSArray *annotations = mapView.annotations;
    NSInteger count = [mapView.annotations count];
    if ( count == 0) { return; }
    MAMapPoint points[count];
    for( int i=0; i<count; i++ )
    {
        CLLocationCoordinate2D coordinate = [(id <MAAnnotation>)[annotations objectAtIndex:i] coordinate];
        points[i] = MAMapPointForCoordinate(coordinate);
    }
    MAMapRect mapRect = [[MAPolygon polygonWithPoints:points count:count] boundingMapRect];
    // 因为,中间的一个大头针居中显示,所以这里的size要减一半.所以乘以二
//    mapRect.size.width = mapRect.size.width * 2;
//    mapRect.size.height = mapRect.size.height * 2;
    
    mapRect.size.width = mapRect.size.width;
    mapRect.size.height = mapRect.size.height;
    
    MACoordinateRegion region = MACoordinateRegionForMapRect(mapRect);
    
    region.span.latitudeDelta  *= CW_ANNOTATION_REGION_PAD_FACTOR;
    region.span.longitudeDelta *= CW_ANNOTATION_REGION_PAD_FACTOR;
    
    if( region.span.latitudeDelta > CW_MAX_DEGREES_ARC ) { region.span.latitudeDelta  = CW_MAX_DEGREES_ARC; }
    if( region.span.longitudeDelta > CW_MAX_DEGREES_ARC ){ region.span.longitudeDelta = CW_MAX_DEGREES_ARC; }
    
    if( region.span.latitudeDelta  < CW_MINIMUM_ZOOM_ARC ) { region.span.latitudeDelta  = CW_MINIMUM_ZOOM_ARC; }
    if( region.span.longitudeDelta < CW_MINIMUM_ZOOM_ARC ) { region.span.longitudeDelta = CW_MINIMUM_ZOOM_ARC; }
    if( count == 1 )
    {
        region.span.latitudeDelta = CW_MINIMUM_ZOOM_ARC;
        region.span.longitudeDelta = CW_MINIMUM_ZOOM_ARC;
    }
//    region.center = self.location1;
    [mapView setRegion:region animated:animated];
}
@end
